<script setup name="Layout">
import { ref, reactive, computed, onMounted, onUnmounted } from 'vue'
import ChineseHoliday from '@chnlib/chinese-holiday'
import CountUp from '@/components/count-up/index.vue'
// 当前时间（响应式）
const now = ref(new Date())

// 配置信息和遮罩
const configInfo = reactive({})
const mask = reactive({ show: true, text: '' })

// 数据展示面板
const statisticData = reactive([
  { title: '发薪', value: -1, unit: '天' },
  { title: '周五', value: -1, unit: '天' },
  { title: '下个节日', value: -1, unit: '天' },
  { title: '今天赚了', value: 0, unit: '￥' }
])

const countdown = ref('00:00:00')
let animationFrameId = null
let hasUpdatedToday = false

// 关闭按钮
const handleClose = () => {
  window.electronAPI.shutdown()
}

// 是否在工作时间
const isInWorkTime = () => {
  const { workTime, offWorkTime } = configInfo
  if (!workTime || !offWorkTime) return false

  const minutes = now.value.getHours() * 60 + now.value.getMinutes()
  const workStart = timeStringToMinutes(workTime)
  const workEnd = timeStringToMinutes(offWorkTime)

  const today = new Date(now.value.getFullYear(), now.value.getMonth(), now.value.getDate())
  return minutes > workStart && minutes < workEnd && ChineseHoliday.isWorkday(today)
}

// 页面标题
const title = ref('下班还有')

// 每秒收入
const secondSalary = computed(() => {
  const { salary = 0, holidayMode = 2, workTime = '09:00', offWorkTime = '18:00' } = configInfo
  if (!salary || !holidayMode) return 0

  const workDaysMap = { 0: 24, 1: 26, 2: 21.5 }
  const workDaysPerMonth = workDaysMap[holidayMode]
  const [startH, startM] = workTime.split(':').map(Number)
  const [endH, endM] = offWorkTime.split(':').map(Number)
  const secondsPerDay = (endH * 60 + endM - startH * 60 - startM) * 60
  return Number((salary / workDaysPerMonth / secondsPerDay).toFixed(6))
})

// 每天更新一次统计数据
const uploadStatisticData = () => {
  const today = now.value
  statisticData[0].value = getSalaryDaysLeft(configInfo.salaryDate)
  const day = today.getDay()
  statisticData[1].value = day <= 5 ? 5 - day : 7 - day + 5
  const next = getNextHolidayInfo(today)
  statisticData[2].value = next.daysLeft
  statisticData[2].title = next.name
  hasUpdatedToday = true
}

// 启动动画更新逻辑
const loopUpdate = () => {
  let lastSecond = null


  const loop = () => {
    const current = new Date()
    const currentSecond = current.getSeconds()

    if (currentSecond !== lastSecond) {
      lastSecond = currentSecond
      now.value = current

      if (isInWorkTime()) {
        countdown.value = getTimeDiffStr(configInfo.offWorkTime, current)
        const [h, m] = configInfo.workTime.split(':').map(Number)
        const start = new Date(current.getFullYear(), current.getMonth(), current.getDate(), h, m, 0)
        const secondsWorked = (current - start) / 1000
        statisticData[3].value = secondsWorked * secondSalary.value
        title.value = '下班还有'
      } else {
        title.value = '当前处于休息时间'
        countdown.value = '00:00:00'
        statisticData[3].value = 0
      }

      const isMidnight = current.getHours() === 0 && current.getMinutes() === 0
      if (isMidnight && !hasUpdatedToday) uploadStatisticData()
      if (!isMidnight && hasUpdatedToday) hasUpdatedToday = false
    }

    animationFrameId = requestAnimationFrame(loop)
  }

  cancelAnimationFrame(animationFrameId)
  loop()
}

// 生命周期钩子
onMounted(async () => {
  try {
    const config = await window.electronAPI.loadConfig()
    Object.assign(configInfo, config)
  } catch (err) {
    console.log('读取配置失败')
    mask.text = '读取配置失败'
    return
  }

  const { workTime, offWorkTime, themeColor } = configInfo
  if (workTime && offWorkTime) {
    mask.show = false
    loopUpdate()
  } else {
    mask.text = '上班时间或下班时间未设置'
  }

  uploadStatisticData()
  if (themeColor) {
    document.documentElement.style.setProperty('--el-color-primary', themeColor)
  }
})

onUnmounted(() => {
  cancelAnimationFrame(animationFrameId)
})

// 工具函数
function timeStringToMinutes(timeStr) {
  const [h, m] = timeStr.split(':').map(Number)
  return h * 60 + m
}

function getTimeDiffStr(toTimeStr, now) {
  const nowSeconds = now.getHours() * 3600 + now.getMinutes() * 60 + now.getSeconds()
  const [h, m] = toTimeStr.split(':').map(Number)
  const targetSeconds = h * 3600 + m * 60
  let diff = Math.abs(targetSeconds - nowSeconds)

  const hh = String(Math.floor(diff / 3600)).padStart(2, '0')
  const mm = String(Math.floor((diff % 3600) / 60)).padStart(2, '0')
  const ss = String(diff % 60).padStart(2, '0')

  return `${hh}:${mm}:${ss}`
}

function getSalaryDaysLeft(day) {
  if (!day) return 0
  const nowDate = now.value
  const year = nowDate.getFullYear()
  const month = nowDate.getMonth()
  const lastDay = new Date(year, month + 1, 0).getDate()
  const safeDay = Math.min(day, lastDay)
  const salaryDate = new Date(year, month, safeDay)
  return Math.ceil((salaryDate - nowDate) / (1000 * 60 * 60 * 24))
}

function getNextHolidayInfo(today) {
  const startStr = today.toISOString().split('T')[0]
  const end = new Date(today)
  end.setFullYear(end.getFullYear() + 1)
  const endStr = end.toISOString().split('T')[0]

  const holidays = ChineseHoliday.findHolidays(startStr, endStr)
  for (const h of holidays) {
    const hDate = new Date(h.date)
    const diff = Math.ceil((hDate - today) / (1000 * 60 * 60 * 24))
    if (diff >= 0) return { name: h.cn, daysLeft: diff, date: h.date }
  }
  return { name: '', daysLeft: -1, date: '' }
}

function formatMoney(val) {
  return Number(val).toFixed(2)
}
</script>

<template>
  <div class="layout">
    <div class="close-btn" @click="handleClose"></div>
    <div v-if="mask.show" class="mask">{{ mask.text }}</div>
    <div class="title">{{ title }}</div>
    <div class="main">
      <div class="content">
        <div class="countdown">{{ countdown }}</div>
        <div class="time-block">
          <div v-for="(item, i) in statisticData" :key="i" class="item">
            <div class="title">{{ item.title }}</div>
            <!-- <div class="value">
              {{ i === 3 ? formatMoney(item.value) : item.value }}
            </div> -->
            <div v-if="i === 3" class="value">
              <CountUp :number="formatMoney(item.value)"/>
            </div>
            <div v-else class="value">{{ item.value }}</div>
            <div class="unit">{{ item.unit }}</div>
          </div>
        </div>
      </div>
      <div class="picture" :style="{ backgroundImage: `url(${configInfo.picture})` }"></div>
    </div>
  </div>
</template>

<style lang="scss">
@use './index';
</style>
